package org.trade.common.client;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

import org.springframework.beans.factory.FactoryBean;
import org.springframework.web.client.RestTemplate;
import org.trade.common.constant.TradeEnums;

/*
 * 动态代理，构建远程调用
 */
public class ResClientProxyFactoryBeanString implements FactoryBean {
	private static RestTemplate restTemplate = new RestTemplate();
	// 接口类
	private Class serviceInterface;
	// 枚举
	private TradeEnums.RestServerEnum serverEnum;

	/** 创建一个动态代理，通过这个代理来实现被代理者在代理中想得到的对象（此对象的方法已经被代理类改变）
	 * 此时，Object.get...
	 */
	public Object getObject() throws Exception {
		// (ClassLoader loader, Class<?>[] interfaces, InvocationHandler h)
		return Proxy.newProxyInstance(getClass().getClassLoader(), new Class[] { serviceInterface }, new ClientProxy());
	}

	public Class getServiceInterface() {
		return serviceInterface;
	}

	public void setServiceInterface(Class serviceInterface) {
		this.serviceInterface = serviceInterface;
	}

	public Class getObjectType() {
		return serviceInterface;
	}

	public boolean isSingleton() {
		return true;
	}

	public static void setRestTemplate(RestTemplate restTemplate) {
		ResClientProxyFactoryBeanString.restTemplate = restTemplate;
	}

	public void setServerEnum(TradeEnums.RestServerEnum serverEnum) {
		this.serverEnum = serverEnum;
	}

	// 作为动态代理，内部类实现InvocationHandler接口。调用common中的api时候会自动开始调用invoke方法，把实际的接口方法转变成代理中的实现方法
	private class ClientProxy implements InvocationHandler {
		public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
			return restTemplate.postForObject(serverEnum.getServerUrl() + method.getName(), args[0],
					method.getReturnType());
		}

	}
}
